#ifndef __AI_H__
#define __AI_H__

#include <QDateTime>
#include <QVector>
#include <QDebug>

#include "config.h"
#include "block.h"

//	游戏中点坐标的结构体

struct Point
{
	int x;
	int y;
};

//	AI程序中记录数字信息的结构体

struct Number
{
	int x;
	int y;
	int value;
};

//	AI程序中记录不确定点的结构体

struct Uncertain
{
	int x;
	int y;
	int mineTimes;
	double probability;
};

//	AI程序返回操作信息的结构体

struct Operation
{
	int x;
	int y;
	int click;
};

//	AI程序中记录游戏界面数据的结构体

struct BlockData
{
	int number;
	bool isFind;
	bool isMarked;
	bool isCovered;
};

/*
 *	AI程序中记录联通块数据的结构体，其成员含义如下:
 *
 *	uncertainList	-> 该联通块中所有不确定的位置列表
 *	numberList		-> 与该联通块相关的所有的数字列表
 *	ansCount		-> 该联通块中合理的解的数量
 */

struct LinkBlock
{
	QVector <Uncertain> uncertainList;
	QVector <Number> numberList;
	int ansCount;
};

//	MineSweeper 游戏的AI类，包含AI算法的具体实现

class MineSweeperAI
{
	// 游戏界面的相关数据

	private:
		BlockData blockData[TABLE_ROWS_MAX][TABLE_COLS_MAX];
		int tableRows;
		int tableCols;
		int uncoverCount;
		int mineLastCount;
		int unknownCount;

	//	AI程序运行时的相关数据列表

	private:
		QVector <Number> numberList;
		QVector <LinkBlock> linkList;
		QVector <Operation> operationList;

	//	基本的点击操作方法

	private:
		void leftClick(Point);
		void rightClick(Point);
		void randClick();

	//	AI程序运行步骤的子函数

	private:
		void getBlockData(Block[TABLE_ROWS_MAX][TABLE_COLS_MAX]);
		void clearData();
		void getNumber();
		void setMark();
		void setUncover();
		bool isUncertain(Point);
		bool findLinkBlock(LinkBlock&, Point);
		void findUncertain(LinkBlock&, Point);
		void getLinkBlockData();
		void removeInvalidLink();
		bool isImpossible(unsigned long long);
		void resetAnswer();
		void setAnswer(LinkBlock&, unsigned long long);
		bool isRightAnswer(LinkBlock&);
		void addAnswerCount(LinkBlock&);
		void getProbability(LinkBlock&);
		void findAnswer();
		void setResult();

	//	AI程序类对外部的唯一接口，该函数获取一定的游戏界面信息，返回一个操作列表

	public:
		QVector <Operation> run(Block[TABLE_ROWS_MAX][TABLE_COLS_MAX], int, int, int);
};

#endif
